Release 10.1A: OpenEdge Development:
.NET Open Clients


ProDataSet examples

This section provides some code examples for ProDataSets.

Note: These samples are not available on the Documentation and Samples CD or Progress Documentation Web site.

Sample static ProDataSet

Example 4–6 is a static ProDataSet definition in a persistent procedure, CustomersAndOrders.p.

Example 4–6: Static ProDataSet in a persistent procedure
DEFINE TEMP-TABLE OrderInfo 
     FIELD order-date AS DATE 
     FIELD quantity AS INTEGER. 
DEFINE TEMP-TABLE CustomerInfo 
     FIELD cust-name AS CHAR 
     FIELD address AS CHAR. 
DEFINE DATASET OrderDS for OrderInfo, CustomerInfo. 
PROCEDURE getOrders: 
     DEFINE OUTPUT PARAM DATASET FOR OrderDS. 

For this parameter, ProxyGen generates the following:

Example 4–7 is a static ProDataSet definition in an external procedure, SetCustomersAndOrders.p.

Example 4–7: Static ProDataSet in a procedure
DEFINE TEMP-TABLE OrderInfo 
     FIELD order-date AS DATE 
     FIELD quantity AS INTEGER. 
DEFINE TEMP-TABLE CustomerInfo 
     FIELD cust-name AS CHAR 
     FIELD address AS CHAR. 
DEFINE DATASET MySetOrderDS for OrderInfo, CustomerInfo. 
DEFINE INPUT PARAM DATASET FOR MySetOrderDS. 

Since the schema for these two static DataSet parameters is the same, ProxyGen uses the previously generated, strongly typed DataSet in the proxy method generated for this external procedure. For example:

public void SetCustomersAndOrders(Acme.StrongTypesNS.OrderDSDataSet 
mySetOrderDS) 

For INPUT and INPUT-OUTPUT parameters, the .NET client code must supply an instance of the strongly typed DataSet object. For OUTPUT parameters, the strongly typed DataSet variable must be declared, but the instance is created by Progress and returned to the .NET client as a parameter.

Sample DATASET-HANDLE parameter

Example 4–8 is a DATASET-HANDLE parameter.

Example 4–8: DATASET-HANDLE parameter
PROCEDURE getOrders: 
     DEFINE OUTPUT PARAMETER DATASET-HANDLE dsetHndl. 

For this parameter, ProxyGen generates the following method in the proxy:

public void getOrders(out System.Data.DataSet dsetHndl) 

For INPUT and INPUT-OUTPUT parameters, the .NET client code must supply an instance of the System.Data.DataSet object. For OUTPUT parameters, the DataSet variable must be declared, but the instance is created by Progress and returned to the .NET client as a parameter.

Sample .NET Open Client application using a ProDataSet

Example 4–9 shows sample code for calling a procedure with a ProDataSet.

Example 4–9: Calling a procedure with an output static ProDataSet
// The specified namespace is Acme 
using Acme.StrongTypesNS; 
// Calling a procedure with an output static ProDataSet. 
Account appObj = new Account("AppServer://myhost/asbroker1", "", "", ""); 
OrderDSDataSet outDS = null; 
// Call the procedure. 
appObj.GetCustomersAndOrders(out outDS); 
// Assign the ProDataSet to a DataGrid. 
myForm.dataGrid1.DataSource = outDS; 
myForm.dataGrid1.DataMember = "Customers"; 
myForm.dataGrid1.ReadOnly = true; 
myForm.dataGrid1.CaptionText = "Number of Customers: " + 
    outDS.Tables["ttCust"].Rows.Count; 

Sample ProDataSet update

The code examples in this section show how to pass a changes-only DataSet (that is, a DataSet that contains only records that have been added, updated, or deleted) to the AppServer and properly process the changes.

Example 4–10 shows one way to handle updates in a .NET Open Client environment.

Note: For the sake of simplicity, this example does not include standard error checking. Make sure that you include error checking in your application code.

Example 4–10: .NET update DataSet procedure
//Define two strongly-typed DataSets 
using Acme.StrongTypesNS; 
dsOrderDataSet dsOrders; 
dsOrderDataSet dsUpdatedRecs; 
      . 
      . 
      . 
// Populate the dsUpdatedRecs DataSet with only the changed rows 
dsUpdatedRecs = (dsOrderDataSet) 
 (dsOrders.GetChanges()); 
// Confirm that there are updates before continuing 
if (dsUpdatedRecs != null)  
   { 
      appObj.UpdateDS(ref dsUpdatedRecs); 
      if (dsUpdateRecs.Tables["orderline"].HasErrors)  
         { 
            displayMessage = "The following Orderline rows were not updated:"; 
            foreach(DataRow failedRow in
                    dsUpdatedRecs.Tables ["orderline"].Rows) 
            { 
               if (failedRow.HasErrors) 
               { 
                 displayMessage += "\n\r Line number: " + 
                       failedRow["linenum"].ToString() +  ",  
                 Error Message: " + failedRow.RowError;  
               } 
                . 
                . 
                . 
            } 
        } 
     } 
else 
   { 
      dspMsg ="All updates succeeded"; 
      dspCaption = "Save completed"; 
      dspButton = MessageBoxButtons.OK; 
      resultDlog = MessageBox.Show(this, dspMsg, dspCaption, dspButton,		
         MessageBoxIcon.Information, 
         MessageBoxDefaultButton.Button1, 
         MessageBoxOptions.RightAlign); 
   } 
// Remove the pending additional order lines before merging to prevent
// duplicate rows if the key fields on the row number were changed during the 
// update.  
foreach(DataRow curRow in dtTableTwo.Select("", "", DataViewRowState.Added)) 
   { 
      dtTableTwo.Rows.Remove(curRow);  
   } 
// Merge the changes 
dsOrders.Merge(dsUpdatedRecs); 
			// Reset the row state for the modified rows now that changes  
dsOrders.AcceptChanges(); 

Example 4–11 shows temp-table definitions in a 4GL include file, sOrderTables.i.

Example 4–11: Include file definition of temp-table definitions
/* dsOrderTables.i -- include file for Temp-Table definitions */ 
DEFINE TEMP-TABLE ttOrder FIELDS (...) 
   INDEX OrderNum IS UNIQUE PRIMARY OrderNum. 
DEFINE TEMP-TABLE ttOLine FIELDS (...) 
   BEFORE-TABLE ttOlineBefore 
   INDEX orderline IS UNIQUE PRIMARY Ordernum Linenum. 

Example 4–12 shows a static ProDataSet definition in a 4GL include file, dsOrderDef.i.

Example 4–12: Include file definition of DataSet dsOrder
/* dsOrderDef.i -- include file definition of DATASET dsOrder. */ 
DEFINE DATASET dsOrder FOR ttOrder, ttOLine 
    DATA-RELATION OrderLine FOR ttOrder, ttOLine 
      RELATION-FIELDS (OrderNum, OrderNum). 

Example 4–13 shows a 4GL procedure that updates the database with a DataSet that contains only records that have been modified (added, updated, or deleted).

Example 4–13: 4GL update DataSet procedure
{OrderTables.i} 
{OrderDS.i} 
DEFINE INPUT-OUTPUT PARAMETER DATASET FOR dsOrder. 
DEFINE DATA-SOURCE srcOline FOR Orderline. 
DEFINE VARIABLE returnValue AS LOGICAL NO-UNDO. 
DEFINE VARIABLE hSrcOline  AS HANDLE NO-UNDO. 
hSrcOline = DATA-SOURCE srcOline:HANDLE.  
BUFFER ttOLine:ATTACH-DATA-SOURCE(hSrcOline).  
FOR EACH ttOlineBefore TRANSACTION: 
    returnValue = BUFFER ttOlineBefore:SAVE-ROW-CHANGES("Orderline") NO-ERROR.  
END.                
DELETE OBJECT hSrcOline.  
RETURN. 


Copyright © 2005 Progress Software Corporation
www.progress.com
Voice: (781) 280-4000
Fax: (781) 280-4095